package item.pickable;

import java.util.*;
import attribute.*;

public class RepairKit extends EnergyItem{
	private final static Energy MAX_ENERGY = new Energy(Integer.MAX_VALUE, EnergyUnit.Wattsecond);
	private static Random random = new Random();
	
	/**
	 * Initialises this new RepairKit with the given X and Y coordinate for the position,
	 * 		the given energy, the given weight 
	 * 		and the given board it has to be placed on.
	 * 
	 * @param X
	 * 		The X coordinate of the repair kits new position on the given board.
	 * @param Y
	 * 		The Y coordinate of the repair kits new position on the given board.
	 * @param energy
	 * 		The amount of energy the repair kit must have.
	 * @param board
	 * 		The board the repair kit must be placed on.
	 * @param weight
	 * 		The weight the repair kit must have.
	 * 
	 * @pre	The given initial energy must be a valid energy for the repair kit
	 * 		|isValidEnergy(energy)
	 * 
	 * @effect The new energy of the repair kit is set to the given energy using setEnergy().
	 * 			|new.getEnergy() = new Energy(energy, EnergyUnit.Wattsecond)
	 * 
	 * @effect The new weight of the repair kit is set to the given weight using setWeight().
	 * 			|This.setWeight(weight)
	 * 
	 * @effect The position and board of the repair kit is set using setValidPosition(X, Y, board)
	 * 			| this.setValidPosition(X, Y, board)
	 */
	public RepairKit(long X, long Y, double energy, int weight, Board board){
		assert this.canHaveAsEnergy(energy, EnergyUnit.Wattsecond);
		this.setEnergy(new Energy(energy, EnergyUnit.Wattsecond));
		this.setWeight(weight);
		this.setValidPosition(X, Y, board);
	}
	
	/**
	 * Initialise a new RepairKit with given energy and weight, who is not on any board or position.
	 * 
	 * @param energy
	 * 			The energy the repair kit must have.
	 * @param weight
	 * 			The weight the repair kit must have.
	 * 
	 * @pre	...
	 * 			|this.isValidEnergy(energy)
	 * 
	 * @effect ...
	 * 			|new.getEnergy() = new Energy(energy, EnergyUnit.Wattsecond)
	 * 
	 * @effect ...
	 * 			|this.setWeight(weight)
	 */
	public RepairKit(double energy, int weight){
		assert this.canHaveAsEnergy(energy, EnergyUnit.Wattsecond);
		this.setEnergy(new Energy(energy, EnergyUnit.Wattsecond));
		this.setWeight(weight);
	}

	/**
	 * Initialise a new RepairKit as a repair kit with -1, -1 and null as its position and board.
	 * 
	 * @effect	This new repair kit is initialised with randomly selected energy and weight.
	 */
	public RepairKit(){
		this(((random.nextInt((int) (getMaxEnergy().getEnergyDouble()/100))) + 1) * 100,
				(random.nextInt(getMaxWeight()/100) + 1) * 100);
	}
	
	
	/**
	 * Returns the max energy of this class.
	 */
	public static Energy getMaxEnergy(){
		return MAX_ENERGY;
	}
	
	/**
	 * Checks whether this repairKit can have the given energy as Energy.
	 * 
	 * @param energy
	 * 			The energyDouble to check.
	 * @param unit 
	 * 			The given unit to check.
	 * 
	 * @return	Returns true if and only if the given energy is bigger or equals the minimum energy 
	 * 				and smaller than or equal to the maximum energy.
	 * 			|result == (new Energy(energy, unit).compareTo(getMinEnergy()) >= 0 
	 *			|	&& new Energy(energy, unit).compareTo(getMaxEnergy()) <= 0)
	 */
	@Override
	public boolean canHaveAsEnergy(double energy, EnergyUnit unit){
		return (new Energy(energy, unit).compareTo(getMinEnergy()) >= 0 
				&& new Energy(energy, unit).compareTo(getMaxEnergy()) <= 0);
	}
	
	@Override
	public boolean hasAtleast(Object condition){
		if(condition.getClass() == int.class){
			if(this.getWeight() >= (Integer)condition)
				return true;
		}
		else if(condition.getClass() == Energy.class){
			if((this.getEnergy().compareTo((Energy)condition)) >= 0)
					return true;
		}
		else if(condition.getClass() == Position.class){
			if((this.getPosition() == ((Position)condition)))
				return true;
		}
		return false;
	}
}